// RAP [rh] Keys completely disabled as not implemented in RWT
///*******************************************************************************
// * Copyright (c) 2007, 2009 IBM Corporation and others.
// * All rights reserved. This program and the accompanying materials
// * are made available under the terms of the Eclipse Public License v1.0
// * which accompanies this distribution, and is available at
// * http://www.eclipse.org/legal/epl-v10.html
// *
// * Contributors:
// *     IBM Corporation - initial API and implementation
// *******************************************************************************/
//
//package org.eclipse.ui.internal.keys.model;
//
//import java.io.BufferedWriter;
//import java.io.FileOutputStream;
//import java.io.IOException;
//import java.io.OutputStreamWriter;
//import java.io.Writer;
//import java.util.Map;
//import java.util.ResourceBundle;
//import org.eclipse.core.commands.CommandManager;
//import org.eclipse.core.commands.ParameterizedCommand;
//import org.eclipse.core.commands.common.NotDefinedException;
//import org.eclipse.core.commands.contexts.ContextManager;
//import org.eclipse.core.runtime.IStatus;
//import org.eclipse.core.runtime.ListenerList;
//import org.eclipse.core.runtime.SafeRunner;
//import org.eclipse.core.runtime.Status;
//import org.eclipse.jface.bindings.Binding;
//import org.eclipse.jface.bindings.BindingManager;
//import org.eclipse.jface.bindings.Scheme;
//import org.eclipse.jface.bindings.keys.KeyBinding;
//import org.eclipse.jface.bindings.keys.KeySequence;
//import org.eclipse.jface.util.IPropertyChangeListener;
//import org.eclipse.jface.util.PropertyChangeEvent;
//import org.eclipse.jface.util.SafeRunnable;
//import org.eclipse.swt.SWT;
//import org.eclipse.swt.widgets.FileDialog;
//import org.eclipse.swt.widgets.Shell;
//import org.eclipse.ui.contexts.IContextService;
//import org.eclipse.ui.internal.WorkbenchPlugin;
//import org.eclipse.ui.internal.keys.KeysPreferencePage;
//import org.eclipse.ui.internal.keys.NewKeysPreferenceMessages;
//import org.eclipse.ui.internal.misc.StatusUtil;
//import org.eclipse.ui.internal.util.Util;
//import org.eclipse.ui.keys.IBindingService;
//import org.eclipse.ui.services.IServiceLocator;
//import org.eclipse.ui.statushandlers.StatusManager;
//
///**
// * @since 3.4
// * 
// */
//public class KeyController {
//	private static final String DELIMITER = ","; //$NON-NLS-1$
//	private static final String ESCAPED_QUOTE = "\""; //$NON-NLS-1$
//	private static final String REPLACEMENT = "\"\""; //$NON-NLS-1$
//	/**
//	 * The resource bundle from which translations can be retrieved.
//	 */
//	private static final ResourceBundle RESOURCE_BUNDLE = ResourceBundle
//			.getBundle(KeysPreferencePage.class.getName());
//	private ListenerList eventManager = null;
//	private BindingManager fBindingManager;
//	private ContextModel contextModel;
//	private SchemeModel fSchemeModel;
//	private BindingModel bindingModel;
//	private boolean notifying = true;
//	private ConflictModel conflictModel;
//	private IServiceLocator serviceLocator;
//
//	private ListenerList getEventManager() {
//		if (eventManager == null) {
//			eventManager = new ListenerList(ListenerList.IDENTITY);
//		}
//		return eventManager;
//	}
//
//	public void setNotifying(boolean b) {
//		notifying = b;
//	}
//
//	public boolean isNotifying() {
//		return notifying;
//	}
//
//	public void firePropertyChange(Object source, String propId, Object oldVal,
//			Object newVal) {
//		if (!isNotifying()) {
//			return;
//		}
//		if (Util.equals(oldVal, newVal)) {
//			return;
//		}
//
//		Object[] listeners = getEventManager().getListeners();
//		PropertyChangeEvent event = new PropertyChangeEvent(source, propId,
//				oldVal, newVal);
//		for (int i = 0; i < listeners.length; i++) {
//			((IPropertyChangeListener) listeners[i]).propertyChange(event);
//		}
//	}
//
//	public void addPropertyChangeListener(IPropertyChangeListener listener) {
//		getEventManager().add(listener);
//	}
//
//	public void removePropertyChangeListener(IPropertyChangeListener listener) {
//		getEventManager().remove(listener);
//	}
//
//	public void init(IServiceLocator locator) {
//		getEventManager().clear();
//		this.serviceLocator = locator;
//		fBindingManager = loadModelBackend(serviceLocator);
//		contextModel = new ContextModel(this);
//		contextModel.init(serviceLocator);
//		fSchemeModel = new SchemeModel(this);
//		fSchemeModel.init(fBindingManager);
//		bindingModel = new BindingModel(this);
//		bindingModel.init(serviceLocator, fBindingManager, contextModel);
//		conflictModel = new ConflictModel(this);
//		conflictModel.init(fBindingManager, bindingModel);
//		addSetContextListener();
//		addSetBindingListener();
//		addSetConflictListener();
//		addSetKeySequenceListener();
//		addSetSchemeListener();
//		addSetModelObjectListener();
//	}
//
//	private static BindingManager loadModelBackend(IServiceLocator locator) {
//		IBindingService bindingService = (IBindingService) locator
//				.getService(IBindingService.class);
//		BindingManager bindingManager = new BindingManager(
//				new ContextManager(), new CommandManager());
//		final Scheme[] definedSchemes = bindingService.getDefinedSchemes();
//		try {
//			Scheme modelActiveScheme = null;
//			for (int i = 0; i < definedSchemes.length; i++) {
//				final Scheme scheme = definedSchemes[i];
//				final Scheme copy = bindingManager.getScheme(scheme.getId());
//				copy.define(scheme.getName(), scheme.getDescription(), scheme
//						.getParentId());
//				if (definedSchemes[i] == bindingService.getActiveScheme()) {
//					modelActiveScheme = copy;
//				}
//			}
//			bindingManager.setActiveScheme(modelActiveScheme);
//		} catch (final NotDefinedException e) {
//			StatusManager.getManager().handle(
//					new Status(IStatus.WARNING, WorkbenchPlugin.PI_WORKBENCH,
//							"Keys page found an undefined scheme", e)); //$NON-NLS-1$
//		}
//		bindingManager.setLocale(bindingService.getLocale());
//		bindingManager.setPlatform(bindingService.getPlatform());
//		bindingManager.setBindings(bindingService.getBindings());
//		return bindingManager;
//	}
//
//	public ContextModel getContextModel() {
//		return contextModel;
//	}
//
//	public SchemeModel getSchemeModel() {
//		return fSchemeModel;
//	}
//
//	public BindingModel getBindingModel() {
//		return bindingModel;
//	}
//
//	public ConflictModel getConflictModel() {
//		return conflictModel;
//	}
//
//	private void addSetContextListener() {
//		addPropertyChangeListener(new IPropertyChangeListener() {
//			public void propertyChange(PropertyChangeEvent event) {
//				if (event.getSource() == contextModel
//						&& CommonModel.PROP_SELECTED_ELEMENT.equals(event
//								.getProperty())) {
//					updateBindingContext((ContextElement) event.getNewValue());
//				}
//			}
//		});
//	}
//
//	private void addSetBindingListener() {
//		addPropertyChangeListener(new IPropertyChangeListener() {
//			public void propertyChange(PropertyChangeEvent event) {
//				if (event.getSource() == bindingModel
//						&& CommonModel.PROP_SELECTED_ELEMENT.equals(event
//								.getProperty())) {
//					BindingElement binding = (BindingElement) event
//							.getNewValue();
//					if (binding == null) {
//						conflictModel.setSelectedElement(null);
//						return;
//					}
//					conflictModel.setSelectedElement(binding);
//					ContextElement context = binding.getContext();
//					if (context != null) {
//						contextModel.setSelectedElement(context);
//					}
//				}
//			}
//		});
//	}
//
//	private void addSetConflictListener() {
//		addPropertyChangeListener(new IPropertyChangeListener() {
//			public void propertyChange(PropertyChangeEvent event) {
//				if (event.getSource() == conflictModel
//						&& CommonModel.PROP_SELECTED_ELEMENT.equals(event
//								.getProperty())) {
//					if (event.getNewValue() != null) {
//						bindingModel.setSelectedElement((ModelElement) event
//								.getNewValue());
//					}
//				}
//			}
//		});
//	}
//
//	private void addSetKeySequenceListener() {
//		addPropertyChangeListener(new IPropertyChangeListener() {
//			public void propertyChange(PropertyChangeEvent event) {
//				if (BindingElement.PROP_TRIGGER.equals(event.getProperty())) {
//					updateTrigger((BindingElement) event.getSource(),
//							(KeySequence) event.getOldValue(),
//							(KeySequence) event.getNewValue());
//				}
//			}
//		});
//	}
//
//	private void addSetModelObjectListener() {
//		addPropertyChangeListener(new IPropertyChangeListener() {
//			public void propertyChange(PropertyChangeEvent event) {
//				if (event.getSource() instanceof BindingElement
//						&& ModelElement.PROP_MODEL_OBJECT.equals(event
//								.getProperty())) {
//					if (event.getNewValue() != null) {
//						BindingElement element = (BindingElement) event
//								.getSource();
//						Object oldValue = event.getOldValue();
//						Object newValue = event.getNewValue();
//						if (oldValue instanceof Binding
//								&& newValue instanceof Binding) {
//							conflictModel.updateConflictsFor(element,
//									((Binding) oldValue).getTriggerSequence(),
//									((Binding) newValue).getTriggerSequence(),
//									false);
//						} else {
//							conflictModel.updateConflictsFor(element, false);
//						}
//
//						ContextElement context = element.getContext();
//						if (context != null) {
//							contextModel.setSelectedElement(context);
//						}
//					}
//				}
//			}
//		});
//	}
//
//	private void addSetSchemeListener() {
//		addPropertyChangeListener(new IPropertyChangeListener() {
//			public void propertyChange(PropertyChangeEvent event) {
//				if (event.getSource() == fSchemeModel
//						&& CommonModel.PROP_SELECTED_ELEMENT.equals(event
//								.getProperty())) {
//					changeScheme((SchemeElement) event.getOldValue(),
//							(SchemeElement) event.getNewValue());
//				}
//			}
//		});
//	}
//
//	/**
//	 * @param oldScheme
//	 * @param newScheme
//	 */
//	protected void changeScheme(SchemeElement oldScheme, SchemeElement newScheme) {
//		if (newScheme == null
//				|| newScheme.getModelObject() == fBindingManager
//						.getActiveScheme()) {
//			return;
//		}
//		try {
//			fBindingManager
//					.setActiveScheme((Scheme) newScheme.getModelObject());
//			bindingModel.refresh(contextModel);
//			bindingModel.setSelectedElement(null);
//		} catch (NotDefinedException e) {
//			// TODO Auto-generated catch block
//			e.printStackTrace();
//		}
//
//	}
//
//	private void updateBindingContext(ContextElement context) {
//		if (context == null) {
//			return;
//		}
//		BindingElement activeBinding = (BindingElement) bindingModel
//				.getSelectedElement();
//		if (activeBinding == null) {
//			return;
//		}
//		String activeSchemeId = fSchemeModel.getSelectedElement().getId();
//		Object obj = activeBinding.getModelObject();
//		if (obj instanceof KeyBinding) {
//			KeyBinding keyBinding = (KeyBinding) obj;
//			if (!keyBinding.getContextId().equals(context.getId())) {
//				final KeyBinding binding = new KeyBinding(keyBinding
//						.getKeySequence(),
//						keyBinding.getParameterizedCommand(), activeSchemeId,
//						context.getId(), null, null, null, Binding.USER);
//				if (keyBinding.getType() == Binding.USER) {
//					fBindingManager.removeBinding(keyBinding);
//				} else {
//					fBindingManager.addBinding(new KeyBinding(keyBinding
//							.getKeySequence(), null, keyBinding.getSchemeId(),
//							keyBinding.getContextId(), null, null, null,
//							Binding.USER));
//				}
//				bindingModel.getBindingToElement().remove(
//						activeBinding.getModelObject());
//
//				fBindingManager.addBinding(binding);
//				activeBinding.fill(binding, contextModel);
//				bindingModel.getBindingToElement().put(binding, activeBinding);
//			}
//		}
//	}
//
//	/**
//	 * @param activeBinding
//	 * @param oldSequence
//	 * @param keySequence
//	 */
//	public void updateTrigger(BindingElement activeBinding,
//			KeySequence oldSequence, KeySequence keySequence) {
//		if (activeBinding == null) {
//			return;
//		}
//		Object obj = activeBinding.getModelObject();
//		if (obj instanceof KeyBinding) {
//			KeyBinding keyBinding = (KeyBinding) obj;
//			if (!keyBinding.getKeySequence().equals(keySequence)) {
//				if (keySequence != null && !keySequence.isEmpty()) {
//					String activeSchemeId = fSchemeModel.getSelectedElement()
//							.getId();
//					ModelElement selectedElement = contextModel
//							.getSelectedElement();
//					String activeContextId = selectedElement == null ? IContextService.CONTEXT_ID_WINDOW
//							: selectedElement.getId();
//					final KeyBinding binding = new KeyBinding(keySequence,
//							keyBinding.getParameterizedCommand(),
//							activeSchemeId, activeContextId, null, null, null,
//							Binding.USER);
//					Map bindingToElement = bindingModel.getBindingToElement();
//					bindingToElement.remove(keyBinding);
//					if (keyBinding.getType() == Binding.USER) {
//						fBindingManager.removeBinding(keyBinding);
//					} else {
//						fBindingManager.addBinding(new KeyBinding(keyBinding
//								.getKeySequence(), null, keyBinding
//								.getSchemeId(), keyBinding.getContextId(),
//								null, null, null, Binding.USER));
//					}
//
//					fBindingManager.addBinding(binding);
//					activeBinding.fill(binding, contextModel);
//					bindingModel.getBindingToElement().put(binding,
//							activeBinding);
//
//					// Remove binding for any system conflicts
//					Object[] keys = bindingToElement.keySet().toArray();
//					for (int i = 0; i < keys.length; i++) {
//						Binding bindingKey = (Binding) keys[i];
//						if (oldSequence.equals(bindingKey.getTriggerSequence())
//								&& bindingKey.getType() == Binding.SYSTEM) {
//							BindingElement be = (BindingElement) bindingToElement
//									.get(bindingKey);
//							bindingModel.remove(be);
//						}
//					}
//
//					bindingModel.setSelectedElement(activeBinding);
//				} else {
//					bindingModel.getBindingToElement().remove(keyBinding);
//					if (keyBinding.getType() == Binding.USER) {
//						fBindingManager.removeBinding(keyBinding);
//					} else {
//						fBindingManager.addBinding(new KeyBinding(keyBinding
//								.getKeySequence(), null, keyBinding
//								.getSchemeId(), keyBinding.getContextId(),
//								null, null, null, Binding.USER));
//					}
//					activeBinding.fill(keyBinding.getParameterizedCommand());
//				}
//			}
//		} else if (obj instanceof ParameterizedCommand) {
//			ParameterizedCommand cmd = (ParameterizedCommand) obj;
//			if (keySequence != null && !keySequence.isEmpty()) {
//				String activeSchemeId = fSchemeModel.getSelectedElement()
//						.getId();
//				ModelElement selectedElement = contextModel
//						.getSelectedElement();
//				String activeContextId = selectedElement == null ? IContextService.CONTEXT_ID_WINDOW
//						: selectedElement.getId();
//				final KeyBinding binding = new KeyBinding(keySequence, cmd,
//						activeSchemeId, activeContextId, null, null, null,
//						Binding.USER);
//				fBindingManager.addBinding(binding);
//				activeBinding.fill(binding, contextModel);
//				bindingModel.getBindingToElement().put(binding, activeBinding);
//			}
//		}
//	}
//
//	/**
//	 * Replaces all the current bindings with the bindings in the local copy of
//	 * the binding manager.
//	 * 
//	 * @param bindingService
//	 *            The binding service that saves the changes made to the local
//	 *            copy of the binding manager
//	 */
//	public void saveBindings(IBindingService bindingService) {
//		try {
//			bindingService.savePreferences(fBindingManager.getActiveScheme(),
//					fBindingManager.getBindings());
//		} catch (IOException e) {
//			logPreferenceStoreException(e);
//		}
//	}
//
//	/**
//	 * Logs the given exception, and opens an error dialog saying that something
//	 * went wrong. The exception is assumed to have something to do with the
//	 * preference store.
//	 * 
//	 * @param exception
//	 *            The exception to be logged; must not be <code>null</code>.
//	 */
//	private final void logPreferenceStoreException(final Throwable exception) {
//		final String message = NewKeysPreferenceMessages.PreferenceStoreError_Message;
//		String exceptionMessage = exception.getMessage();
//		if (exceptionMessage == null) {
//			exceptionMessage = message;
//		}
//		final IStatus status = new Status(IStatus.ERROR,
//				WorkbenchPlugin.PI_WORKBENCH, 0, exceptionMessage, exception);
//		WorkbenchPlugin.log(message, status);
//		StatusUtil.handleStatus(message, exception, StatusManager.SHOW);
//	}
//
//	/**
//	 * Filters contexts for the When Combo.
//	 * 
//	 * @param actionSets
//	 *            <code>true</code> to filter action set contexts
//	 * @param internal
//	 *            <code>false</code> to filter internal contexts
//	 * 
//	 */
//	public void filterContexts(boolean actionSets, boolean internal) {
//		contextModel.filterContexts(actionSets, internal);
//	}
//
//	/**
//	 * Sets the bindings to default.
//	 * 
//	 * @param bindingService
//	 */
//	public void setDefaultBindings(IBindingService bindingService) {
//		// Fix the scheme in the local changes.
//		final String defaultSchemeId = bindingService.getDefaultSchemeId();
//		final Scheme defaultScheme = fBindingManager.getScheme(defaultSchemeId);
//		try {
//			fBindingManager.setActiveScheme(defaultScheme);
//		} catch (final NotDefinedException e) {
//			// At least we tried....
//		}
//
//		// Restore any User defined bindings
//		Binding[] bindings = fBindingManager.getBindings();
//		for (int i = 0; i < bindings.length; i++) {
//			if (bindings[i].getType() == Binding.USER) {
//				fBindingManager.removeBinding(bindings[i]);
//			}
//		}
//
//		bindingModel.refresh(contextModel);
//		saveBindings(bindingService);
//	}
//
//	public void exportCSV(Shell shell) {
//		final FileDialog fileDialog = new FileDialog(shell, SWT.SAVE
//				| SWT.SHEET);
//		fileDialog.setFilterExtensions(new String[] { "*.csv" }); //$NON-NLS-1$
//		fileDialog.setFilterNames(new String[] { Util.translateString(
//				RESOURCE_BUNDLE, "csvFilterName") }); //$NON-NLS-1$
//		fileDialog.setOverwrite(true);
//		final String filePath = fileDialog.open();
//		if (filePath == null) {
//			return;
//		}
//
//		final SafeRunnable runnable = new SafeRunnable() {
//			public final void run() throws IOException {
//				Writer fileWriter = null;
//				try {
//					fileWriter = new BufferedWriter(new OutputStreamWriter(
//							new FileOutputStream(filePath), "UTF-8")); //$NON-NLS-1$
//					final Object[] bindingElements = bindingModel.getBindings()
//							.toArray();
//					for (int i = 0; i < bindingElements.length; i++) {
//						final BindingElement be = (BindingElement) bindingElements[i];
//						if (be.getTrigger() == null
//								|| be.getTrigger().isEmpty()) {
//							continue;
//						}
//						StringBuffer buffer = new StringBuffer();
//						buffer.append(ESCAPED_QUOTE
//								+ Util.replaceAll(be.getCategory(),
//										ESCAPED_QUOTE, REPLACEMENT)
//								+ ESCAPED_QUOTE + DELIMITER);
//						buffer.append(ESCAPED_QUOTE + be.getName()
//								+ ESCAPED_QUOTE + DELIMITER);
//						buffer.append(ESCAPED_QUOTE + be.getTrigger().format()
//								+ ESCAPED_QUOTE + DELIMITER);
//						buffer.append(ESCAPED_QUOTE + be.getContext().getName()
//								+ ESCAPED_QUOTE);
//						buffer.append(System.getProperty("line.separator")); //$NON-NLS-1$
//						fileWriter.write(buffer.toString());
//					}
//
//				} finally {
//					if (fileWriter != null) {
//						try {
//							fileWriter.close();
//						} catch (final IOException e) {
//							// At least I tried.
//						}
//					}
//
//				}
//			}
//		};
//		SafeRunner.run(runnable);
//	}
//}
